/*
 * @Description: 一个校验的工具类 https://blog.csdn.net/xuefeiliuyuxiu/article/details/79352355
 * @Author: yingying.fan
 * @Date: 2019-03-19 16:57:37
 * @Last Modified by: yingying.fan
 * @Last Modified time: 2019-03-19 17:08:16
 */
import { dateFtt } from 'vue-xiaobu-utils'

const vcity = {
  11: '北京',
  12: '天津',
  13: '河北',
  14: '山西',
  15: '内蒙古',
  21: '辽宁',
  22: '吉林',
  23: '黑龙江',
  31: '上海',
  32: '江苏',
  33: '浙江',
  34: '安徽',
  35: '福建',
  36: '江西',
  37: '山东',
  41: '河南',
  42: '湖北',
  43: '湖南',
  44: '广东',
  45: '广西',
  46: '海南',
  50: '重庆',
  51: '四川',
  52: '贵州',
  53: '云南',
  54: '西藏',
  61: '陕西',
  62: '甘肃',
  63: '青海',
  64: '宁夏',
  65: '新疆',
  71: '台湾',
  81: '香港',
  82: '澳门',
  91: '国外'
}

const powers = [7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2]
const paritys = ['1', '0', 'X', '9', '8', '7', '6', '5', '4', '3', '2']

let checkCard = function(card) {
  if (
    card &&
    isCardNo(card) &&
    checkProvince(card) &&
    checkBirthday(card) &&
    checkParity(card)
  ) {
    return true
  }
  return false
}

// 检查号码是否符合规范，包括长度，类型
let isCardNo = function(card) {
  // 身份证号码为15位或者18位，15位时全为数字，18位前17位为数字，最后一位是校验位，可能为数字或字符X
  let reg = /(^\d{15}$)|(^\d{17}(\d|X)$)/
  if (reg.test(card) === false) {
    return false
  }
  return true
}

// 取身份证前两位,校验省份
let checkProvince = function(card) {
  let province = card.substr(0, 2)
  if (vcity[province] === undefined) {
    return false
  }
  return true
}

// 检查生日是否正确
let checkBirthday = function(card) {
  let len = card.length
  // 身份证15位时，次序为省（3位）市（3位）年（2位）月（2位）日（2位）校验位（3位），皆为数字
  if (len === 15) {
    let reFifteen = /^(\d{6})(\d{2})(\d{2})(\d{2})(\d{3})$/
    let arrData = card.match(reFifteen)
    let year = arrData[2]
    let month = arrData[3]
    let day = arrData[4]
    let dataStr = '19' + year + '/' + month + '/' + day
    // return verifyBirthday('19' + year, month, day, birthday)
    return dateFtt('yyyy/MM/dd', new Date(dataStr)) === dataStr
  } else if (len === 18) {
    // 身份证18位时，次序为省（3位）市（3位）年（4位）月（2位）日（2位）校验位（4位），校验位末尾可能为X
    let reEighteen = /^(\d{6})(\d{4})(\d{2})(\d{2})(\d{3})([0-9]|X)$/
    let arrData = card.match(reEighteen)
    let year = arrData[2]
    let month = arrData[3]
    let day = arrData[4]
    let dataStr = year + '/' + month + '/' + day
    // return verifyBirthday(year, month, day, birthday)
    return dateFtt('yyyy/MM/dd', new Date(dataStr)) === dataStr
  }
  return false
}

// 校验位的检测
let checkParity = function(card) {
  // 15位转18位
  card = changeFivteenToEighteen(card)
  let len = card.length
  if (len === 18) {
    let cardTemp = 0
    let valnum
    for (let i = 0; i < 17; i++) {
      cardTemp += card.substr(i, 1) * powers[i]
    }
    valnum = paritys[cardTemp % 11]
    if (valnum === card.substr(17, 1)) {
      return true
    }
    return false
  }
  return false
}

// 15位转18位身份证号
let changeFivteenToEighteen = function(card) {
  if (card.length === 15) {
    let cardTemp = 0
    card = card.substr(0, 6) + '19' + card.substr(6, card.length - 6)
    for (let i = 0; i < 17; i++) {
      cardTemp += card.substr(i, 1) * powers[i]
    }
    card += paritys[cardTemp % 11]
    return card
  }
  return card
}

export { checkCard }
